# import json
# import uuid
# from abc import ABC, abstractmethod
# import sys
# from random import random
#
# from rest_framework.response import  Response
# import time
# from django.shortcuts import redirect
# import requests
# import qrcode
# from io import BytesIO
# import base64
# from django.http import JsonResponse, HttpResponse, HttpResponseRedirect
#
#
# from doc.boss.home import models
# from doc.boss.user import userser
# from doc.boss.user.models import User, Role
# from doc.boss.utils.JWTTool import jwtTool
#
#
# # 定义一个抽象类
# class Factory(ABC):
#     @abstractmethod
#     def geturl(self):
#         pass
#
#     @abstractmethod
#     def callback(self, code):
#         pass
#
#
# # 具体实现类 qq
# class Qq(Factory):
#     def geturl(self, request):
#         login_success_url = "http://127.0.0.1:8000/user/qq-success/"
#         qr = qrcode.QRCode(box_size=10, border=4)
#         qr.add_data(login_success_url)
#         qr.make(fit=True)
#         img = qr.make_image(fill_color="black", back_color="white")
#         buffer = BytesIO()
#         img.save(buffer, format="PNG")
#         img_str = base64.b64encode(buffer.getvalue()).decode()
#         return JsonResponse({
#             "qr_code": f"data:image/png;base64,{img_str}",
#             "login_url": login_success_url,
#             "msg": "QQ登录二维码已生成"
#         })
#
#     def callback(self, request):
#         # 通过 code 获取用户信息
#         default_role = Role.objects.first()
#         if not default_role:
#             return JsonResponse({
#                 "error": "系统错误",
#                 "msg": "请先在后台创建至少一个角色"
#             }, status=500)
#         mock_qq_user = {
#             'openid': f'qq_openid_{random.randint(10000, 99999)}',
#             'nickname': f'QQ用户{random.randint(1000, 9999)}',
#             'avatar': 'https://qlogo.cn/qqapp/102795359/default/100'
#         }
#         user, created = User.objects.get_or_create(
#             phone=mock_qq_user['openid'],
#             defaults={
#                 'role': default_role
#             }
#         )
#         # 生成一个假的token
#         fake_token = str(uuid.uuid4())
#         user_info = {
#             "userid": user.id,
#             "username": mock_qq_user['nickname'],
#             "openid": mock_qq_user['openid'],
#             "nickname": mock_qq_user['nickname'],
#             "avatar": mock_qq_user['avatar']
#         }
#         html_content = f"""
#                 <!DOCTYPE html>
#                 <html>
#                 <head>
#                     <meta charset="UTF-8">
#                     <title>QQ登录成功</title>
#                     <style>
#                         body {{
#                             font-family: Arial, sans-serif;
#                             text-align: center;
#                             padding: 50px;
#                             background-color: #f0f8ff;
#                             margin: 0;
#                         }}
#                         .success-container {{
#                             max-width: 400px;
#                             margin: 0 auto;
#                             padding: 30px;
#                             background-color: white;
#                             border-radius: 8px;
#                             box-shadow: 0 2px 10px rgba(0,0,0,0.1);
#                         }}
#                         .success-icon {{
#                             color: #28a745;
#                             font-size: 48px;
#                             margin-bottom: 20px;
#                         }}
#                         .user-info {{
#                             margin: 20px 0;
#                             padding: 15px;
#                             background-color: #f8f9fa;
#                             border-radius: 4px;
#                         }}
#                         .avatar {{
#                             width: 60px;
#                             height: 60px;
#                             border-radius: 50%;
#                             margin-bottom: 10px;
#                         }}
#                         .close-btn {{
#                             background-color: #6c757d;
#                             color: white;
#                             padding: 10px 20px;
#                             border: none;
#                             border-radius: 4px;
#                             cursor: pointer;
#                             margin-top: 20px;
#                         }}
#                         .close-btn:hover {{
#                             background-color: #5a6268;
#                         }}
#                     </style>
#                 </head>
#                 <body>
#                     <div class="success-container">
#                         <div class="success-icon">✓</div>
#                         <h2>QQ登录成功！</h2>
#                         <div class="user-info">
#                             <img src="{user_info['avatar']}" alt="头像" class="avatar">
#                             <p><strong>用户名：</strong>{user_info['nickname']}</p>
#                             <p><strong>OpenID：</strong>{user_info['openid']}</p>
#                         </div>
#                         <p>正在自动关闭页面...</p>
#                         <button class="close-btn" onclick="closeWindow()">关闭页面</button>
#                     </div>
#
#                     <script>
#                         localStorage.setItem('qq_token', '{fake_token}');
#                         localStorage.setItem('qq_user_info', JSON.stringify({user_info}));
#                         setTimeout(() => {{
#                             closeWindow();
#                         }}, 3000);
#
#                         function closeWindow() {{
#                             try {{
#                                 window.close();
#                             }} catch (e) {{
#                                 // 如果无法关闭，显示提示
#                                 document.body.innerHTML = '<div style="text-align:center;padding:50px;"><h2>登录成功！</h2><p>可以关闭此页面了。</p></div>';
#                             }}
#                         }}
#                     </script>
#                 </body>
#                 </html>
#                 """
#
#         return HttpResponse(html_content, content_type='text/html')
#
#
# # 具体实现类 dingding
# class Dingding(Factory):
#     def geturl(self,request):
#         # 生成随机状态码，防止CSRF攻击
#         state = str(uuid.uuid4())
#         request.session['dingtalk_state'] = state
#
#         # 构建钉钉授权URL
#         redirect_uri = "http://localhost:8000/user/callback/"  # 回调地址-下一个接口
#         # 钉钉应用配置
#         DINGTALK_APPID = 'dinglyrgo3vzh4tgz09p'  # 钉钉开放平台应用ID  APPKey
#
#         url = f"https://login.dingtalk.com/oauth2/auth?redirect_uri={redirect_uri}&response_type=code&client_id={DINGTALK_APPID}&scope=openid corpid&state={state}&prompt=consent"
#         # url=f"https://login.dingtalk.com/oauth2/auth?redirect_uri=http://localhost:8000/user/callback/&response_type=code&client_id=dinglyrgo3vzh4tgz09p&scope=openid corpid&state=state&prompt=consent"
#         return Response({"code": 200, "msg": '获取成功！', "url": url})
#
#     def callback(self, request):
#         # 获取前端参数code
#         code = request.query_params.get('code')
#         if not code:
#             return Response('/?error=钉钉授权失败')
#         url = "https://api.dingtalk.com/v1.0/oauth2/userAccessToken"
#
#         # 根据code获取用户accessToken
#         data = {
#             "clientId": "dinglyrgo3vzh4tgz09p",
#             "clientSecret": "qv3DPWXqcxr0mSv9B6S2eaExQth7TdxMBzSd4gdemXEKlEPJaJ4th7jtb4ubwwdc",
#             "code": code,
#             "grantType": "authorization_code"
#         }
#         response = requests.post(url, json=data).json()
#         print("钉钉返回：", response)  # 调试用
#
#         # 使用 code 向钉钉服务器请求 accessToken
#         if "accessToken" not in response:
#             return Response({"code": 500, "msg": "钉钉授权失败", "detail": response})
#         accessToken = response["accessToken"]
#         # uid = response["openId"]
#
#         # 根据accessToken获取用户信息
#         user_info_url = "https://api.dingtalk.com/v1.0/contact/users/me"
#         headers = {"x-acs-dingtalk-access-token": accessToken}
#         user_info = requests.get(user_info_url, headers=headers).json()
#         print("钉钉用户信息：", user_info)
#
#         if "openId" not in user_info:
#             return Response({"code": 500, "msg": "获取钉钉用户信息失败", "detail": user_info})
#
#         uid = user_info["openId"]
#         name = user_info.get('nick')
#         phone = user_info.get('mobile')
#
#         # 登录 获取第三方登录表 和 用户表
#         third = models.ThirdLogin.objects.filter(oauth_id=uid, style='dingding').first()  # oauth_id第三方登录id
#         if not third:
#             # 写入用户表  手机号用户存在直接绑定  手机号不存在则创建用户
#             user = models.User.objects.filter(phone=phone).first()
#             if not user:
#                 userinfo = {
#                     "phone": phone,
#                     "role": 1
#                 }
#                 u = userser.UserSerializer(data=userinfo)
#                 if u.is_valid():
#                     user = u.save()
#                 else:
#                     print(u.errors)  # 打印验证错误信息
#                     return Response({"code": 500, "msg": '用户创建失败', "errors": u.errors})
#             # 写入第三方登录表
#             thinfo = {
#                 "oauth_id": uid,
#                 "style": "dingding",
#                 "token": accessToken,
#                 "userid": user.id
#             }
#             t = userser.ThirdLoginSerializer(data=thinfo)
#             if t.is_valid():
#                 t.save()
#             else:
#                 return Response({"code": 500, "msg": '第三方登录创建失败'})
#         else:
#             user = third.userid
#             user.token = accessToken
#             user.save()
#
#         # 生成jwt token并返回前端
#         payload = {"user_id": user.id}
#         token = jwtTool.generate_token(payload)
#         payload["exp"] = int(time.time() + 60 * 60 * 24 * 2)
#         refreshToken = jwtTool.generate_token(payload)
#         # 这里改为重定向
#         redirect_url = f"http://localhost:5173/home/?token={token}&retoken={refreshToken}&userid={user.id}"
#         return HttpResponseRedirect(redirect_url)
#
#
# # 具体实现类 dingding  gitee
# class Gitee(Factory):
#     def geturl(self,request):
#         """跳转到Gitee授权页面"""
#         clientID="98c2a9affee7aa2cd9dcbe2f74ee91f0a7345374a4c2cc029c6fdf2828607f8b"
#         clientSecret="8953980345edb1881de15b177a93dfd38709e5585fc930b1eff3f8ea215588b1"
#         clientURL = 'http://localhost:8000/user/callback/'  # 回调地址
#         # 生成随机state防止CSRF攻击
#         state = str(uuid.uuid4())
#         request.session['gitee_auth_state'] = state
#
#         # 构造授权URL
#         auth_url = (
#             f"https://gitee.com/oauth/authorize?"
#             f"client_id={clientID}&"
#             f"redirect_uri={clientURL}&"
#             f"response_type=code&"
#             f"state={state}"
#         )
#         return redirect(auth_url)
#
#     def callback(self, request):
#         """处理 Gitee 回调，获取 access_token 和用户信息"""
#         # 获取授权码
#         code = request.GET.get('code')
#         if not code:
#             return HttpResponse("授权失败，未获取到授权码", status=400)
#
#         # 通过授权码获取 access_token
#         token_url = 'https://gitee.com/oauth/token'
#         data = {
#             'grant_type': 'authorization_code',
#             'code': code,
#             'client_id': "98c2a9affee7aa2cd9dcbe2f74ee91f0a7345374a4c2cc029c6fdf2828607f8b",
#             'client_secret': "8953980345edb1881de15b177a93dfd38709e5585fc930b1eff3f8ea215588b1",
#             'redirect_uri': "http://localhost:8000/user/callback/",
#         }
#
#         # 发送请求获取 token
#         response = requests.post(token_url, data=data)
#         response.raise_for_status()  # 检查请求是否成功
#         token_data = response.json()
#         access_token = token_data.get('access_token')
#
#         if not access_token:
#             return HttpResponse("获取 access_token 失败", status=400)
#
#         # 使用 access_token 获取用户信息
#         user_info_url = f'https://gitee.com/api/v5/user?access_token={access_token}'
#         user_response = requests.get(user_info_url)
#         user_response.raise_for_status()
#         user_data = user_response.json()
#
#         # 根据accessToken获取用户信息
#         user_info_url = "https://api.dingtalk.com/v1.0/contact/users/me"
#         headers = {"x-acs-dingtalk-access-token": access_token}
#         user_info = requests.get(user_info_url, headers=headers).json()
#         print("钉钉用户信息：", user_info)
#
#         if "openId" not in user_info:
#             return Response({"code": 500, "msg": "获取钉钉用户信息失败", "detail": user_info})
#
#         uid = user_info["openId"]
#         name = user_info.get('nick')
#         phone = user_info.get('mobile')
#
#         # 登录 获取第三方登录表 和 用户表
#         third = models.ThirdLogin.objects.filter(oauth_id=uid, style='Gitee').first()  # oauth_id第三方登录id
#         if not third:
#             # 写入用户表  手机号用户存在直接绑定  手机号不存在则创建用户
#             user = models.User.objects.filter(phone=phone).first()
#             if not user:
#                 userinfo = {
#                     "phone": phone,
#                     "role": 1
#                 }
#                 u = userser.UserSerializer(data=userinfo)
#                 if u.is_valid():
#                     user = u.save()
#                 else:
#                     print(u.errors)  # 打印验证错误信息
#                     return Response({"code": 500, "msg": '用户创建失败', "errors": u.errors})
#             # 写入第三方登录表
#             thinfo = {
#                 "oauth_id": uid,
#                 "style": "Gitee",
#                 "token": access_token,
#                 "userid": user.id
#             }
#             t = userser.ThirdLoginSerializer(data=thinfo)
#             if t.is_valid():
#                 t.save()
#             else:
#                 return Response({"code": 500, "msg": '第三方登录创建失败'})
#         else:
#             user = third.userid
#             user.token = access_token
#             user.save()
#
#         # 生成jwt token并返回前端
#         payload = {"user_id": user.id}
#         token = jwtTool.generate_token(payload)
#         payload["exp"] = int(time.time() + 60 * 60 * 24 * 2)
#         refreshToken = jwtTool.generate_token(payload)
#         # 这里改为重定向
#         redirect_url = f"http://localhost:5173/home/?token={token}&retoken={refreshToken}&userid={user.id}"
#         return HttpResponseRedirect(redirect_url)
#
#
# # 定义一个产品类
# class ThirdPartyLogin:
#     def get_sl_class(self, types):
#         # 将小写的类型名转换为大写开头的类名
#         class_name = types.capitalize()
#         # 获取当前模块
#         current_module = sys.modules[__name__]
#         try:
#             # 使用反射获取类对象
#             target_class = getattr(current_module, class_name)
#             if issubclass(target_class, Factory):
#                 return target_class()
#         except AttributeError:
#             print(f"未找到名为 {class_name} 的类。")
#         return None
#
#
# p = ThirdPartyLogin()
# # # 工厂模式 第三方登录
# from doc.boss.tools.tool_login import p
# class WbLogin(APIView):
#     def get(self, request):
#         types = request.GET.get('types')
#         class_name = p.get_sl_class(types)
#         # url = class_name.geturl()
#         return Response(class_name.geturl())
#
